seqblock1 <- function(id.vars, id.vals, exact.vars = NULL, exact.vals = NULL, exact.restr = NULL, covar.vars = NULL, covar.vals = NULL, covar.restr = NULL, covars.ord = NULL, n.tr = 2, tr.names = NULL, assg.prob = NULL, seed = NULL, assg.prob.stat = "mean", trim = .1, assg.prob.method = "ktimes", assg.prob.kfac = 2, file.name = NULL, query = FALSE, verbose = TRUE){
	
	if(query == TRUE){
		## ID
		lid <- readline("How many identification variables are there?  ")
		id.vars <- id.vals <- NULL
		for(ii in 1:lid){
			tmp <- readline(cat("Enter the name of ID variable ", ii, " without quotation marks.", sep="")) 
			id.vars <- append(id.vars, tmp)
			tmp2 <- readline(cat("Enter the value of '", tmp, "'.  ", sep="")) 
			id.vals <- append(id.vals, tmp2)
		}
		nnn <- readline("Should the ID values be numeric? [y/n]  ")
		if(!(substr(nnn,1,1) %in% c("y", "n"))){
			ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
			if(substr(ddd, 1, 1) != "n"){
				}else{
					nnn <- readline("Should the ID values be numeric? [y/n]  ")
				}
		}
		if(substr(nnn,1,1) != "n"){
			id.vals <- as.numeric(id.vals)
		}
		if(sum(is.na(id.vals)) > 0){
			tmp <- readline(cat("Warning: ID value(s)", which(is.na(id.vals)), "was/were coerced to and stored as `NA'.  Proceed? [y/n] ", sep=" "))
		   if(!(substr(tmp,1,1) %in% c("y", "n"))){
			  ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
			  if(substr(ddd, 1, 1) != "n"){
				  }else{
						tmp <- readline(cat("Warning: ID value(s)", which(is.na(id.vals)), "was/were coerced to and stored as `NA'.  Proceed? [y/n] ", sep=" "))				   
				  }
		   }
			if(substr(tmp,1,1) == "n"){
				stop()
			}
		}
		
		## EXACT
		lex <- readline("`Exact blocking variables' are those on which you require covariate values to be identical.  How many exact blocking variables are there?  ")
		exact.vars <- exact.vals <- exact.restr <- NULL
		if(lex > 0){
			for(ii in 1:lex){
				tmp <- readline(cat("Enter the name of exact block variable ", ii, " without quotation marks.", sep="")) 
				exact.vars <- append(exact.vars, tmp)
				tmp2 <- readline(cat("Enter the value of '", tmp, "'.  ", sep="")) 
				tmp3 <- readline(cat("Should '", tmp, "' be restricted to certain values? [n/y]  ", sep=""))
				if(!(substr(tmp3,1,1) %in% c("y", "n"))){
					ddd <- readline("The default is 'no'.  Continue? [y/n]  ")
					if(substr(ddd, 1, 1) != "n"){
						}else{
						tmp3 <- readline(cat("Should '", tmp, "' be restricted to certain values? [n/y]  "))
					}
				}

				if(substr(tmp3,1,1) == "y"){
					tmp4 <- readline(cat("How many values can '", tmp, "' take?  ", sep=""))
					if(tmp4 < 1){
						stop("Restricted variables must have at least one valid value.  ")	
					}
					exact.restr <- as.list(exact.restr)
					exact.restr[[tmp]] <- NA
					for(rrr in 1:tmp4){
						tmp5 <- readline(cat("Enter possible value for '", tmp, "' number ", rrr, sep=""))

						exact.restr[[tmp]] <- append(exact.restr[[tmp]], tmp5) 						
					}
				}
				exact.vals <- append(exact.vals, tmp2)			}				
			nnn <- readline("Should the exact block values be numeric? [y/n]  ")
			if(!(substr(nnn,1,1) %in% c("y", "n"))){
				ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
				if(substr(ddd, 1, 1) != "n"){
					}else{
						nnn <- readline("Should the exact block values be numeric? [y/n]  ")						
					}
			}

			if(substr(nnn,1,1) != "n"){
				exact.vals <- as.numeric(exact.vals)
				if(length(exact.restr) > 0){
					for(rrr in 1:length(exact.restr)){
						exact.restr[[rrr]] <- as.numeric(exact.restr[[rrr]])
					}
				}
			}
			
			if(sum(is.na(exact.vals)) > 0){
				tmp <- readline(cat("Warning: Exact blocking value(s)", which(is.na(exact.vals)), "was/were coerced to and stored as `NA'.  Proceed? [y/n] ", sep=" "))
				if(!(substr(tmp, 1, 1) %in% c("y", "n"))){
					ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
					if(substr(ddd, 1, 1) != "n"){
						}else{
							tmp <- readline(cat("Warning: Exact blocking value(s)", which(is.na(exact.vals)), "was/were coerced to and stored as `NA'.  Proceed? [y/n] ", sep=" "))
					}
				}
				if(substr(tmp,1,1) == "n"){
					stop()
				}
			}
			
		## CHECK that each exact.val is in exact.restr here.
		}
		
		## COVARIATES
		lcv <- readline("How many other blocking variables are there?  ")
		covar.vars <- covar.vals <- covar.restr <- NULL
		if(lcv > 0){
			for(ii in 1:lcv){
				tmp <- readline(cat("Enter the name of blocking variable ", ii, " without quotation marks.", sep="")) 
				covar.vars <- append(covar.vars, tmp)
				tmp2 <- readline(cat("Enter the value of '", tmp, "'.  ", sep="")) 
				tmp3 <- readline(cat("Should '", tmp, "' be restricted to certain values? [n/y]  ", sep=""))
				if(!(substr(tmp3,1,1) %in% c("y", "n"))){
					ddd <- readline("The default is 'no'.  Continue? [y/n]  ")
					if(substr(ddd, 1, 1) != "n"){
						}else{
						tmp3 <- readline(cat("Should '", tmp, "' be restricted to certain values? [n/y]  ", sep=""))
					}
				}

				if(substr(tmp3,1,1) == "y"){
					tmp4 <- readline(cat("How many values can '", tmp, "' take?  ", sep=""))
					if(tmp4 < 1){
						stop("Restricted variables must have at least one valid value.  ")	
					}
					covar.restr <- as.list(covar.restr)
					covar.restr[[tmp]] <- NA
					for(rrr in 1:tmp4){
						tmp5 <- readline(cat("Enter possible value for '", tmp, "' number ", rrr, sep=""))
						covar.restr[[tmp]] <- append(covar.restr[[tmp]], tmp5) 						
					}
				}
				covar.vals <- append(covar.vals, tmp2)
			}				
			nnn <- readline("Should the blocking values be numeric? [y/n]  ")
			
			if(!(substr(nnn,1,1) %in% c("y", "n"))){
				ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
				if(substr(ddd, 1, 1) != "n"){
					}else{
						nnn <- readline("Should the blocking values be numeric? [y/n]  ")						
					}
			}
			
			if(substr(nnn,1,1) != "n"){
				covar.vals <- as.numeric(covar.vals)
			}else{stop("The blocking variables are stored as character strings.\nCurrent implementation does not support distance calculations for character strings.")}  ## change to warning() when categorical distances incorporated
		
			if(sum(is.na(covar.vals)) > 0){
				tmp <- readline(cat("Warning: Blocking value(s)", which(is.na(covar.vals)), "was/were coerced to and stored as `NA'.  Proceed? [y/n] ", sep=" "))
			
				if(!(substr(tmp,1,1) %in% c("y", "n"))){
				ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
					if(substr(ddd, 1, 1) != "n"){
						}else{
							tmp <- readline(cat("Warning: Blocking value(s)", which(is.na(covar.vals)), "was/were coerced to and stored as `NA'.  Proceed? [y/n] ", sep=" "))
						}
					}						
				if(substr(tmp,1,1) == "n"){
					stop()
				}
			}
		
		## Covariates' order
			nnn <- readline("Would you like to specify the order in which blocking variables will be used while (number units considered) < (number covariates + 2) ?  (If not, covariates will be added as possible in the order in which they were entered.)  [n/y]  ")
			if(!(substr(nnn,1,1) %in% c("y", "n"))){
				ddd <- readline("The default is `no'.  Continue? [y/n]  ")
					if(substr(ddd, 1, 1) != "n"){
						}else{
							nnn <- readline(cat("Would you like to specify the order in which blocking variables will be used while (number units considered) < (number covariates +2) ? [n/y]  "))
						}
			}							
			if(substr(nnn,1,1) == "y"){
				for(ii in 1:lcv){
					tmp <- readline(cat("Enter the name of blocking variable prioritized number ", ii, ".", sep=""))
#					if(!(tmp %in% names(x)[(lid+lex+1):(lid+lex+lcv)])){
					if(!(tmp %in% covar.vars)){
						tmp <- readline(cat("`", tmp, "' is not a blocking variable.  Please try again.  Enter the name of blocking variable prioritized number ", ii, ".", sep=""))
					}
					if(tmp %in% covars.ord){
						tmp <- readline(cat("`", tmp, "' has already been prioritized.  Please try again.  Enter the name of blocking variable prioritized number ", ii, ".", sep=""))
					}
					covars.ord <- append(covars.ord, tmp)
				}
			}
		}
		
		## Number of treatment conditions:
    n.tr <- readline("How many experimental/treatment conditions are there?  ")
		n.tr <- as.numeric(n.tr)

		## Names of treatment conditions:
    nnn <- readline(cat("Would you like to specify the names of the experimental conditions? [y/n]  [If not, `Treatment 1', ..., `Treatment ", n.tr, "', will be used]  ", sep=""))
		if(substr(nnn,1,1) != "n"){
		tr.names <- NULL
			for(ii in 1:n.tr){
				tmp <- readline(cat("Enter the name of experimental condition ", ii, " without quotation marks.", sep="")) 
				tr.names <- append(tr.names, tmp)
			}					
		}
		
		## Initial condition assignment probabilities:
    nnn <- readline("Would you like to specify the initial assignment probabilities?  [y/n]  [If not, all treatment assignment probabilities for the first unit will be equal.]  ")
    
    if(!(substr(nnn,1,1) %in% c("y", "n"))){
      ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
      if(substr(ddd, 1, 1) != "n"){
      }else{
          nnn <- readline("Would you like to specify the initial assignment probabilities?  [y/n]  [If not, all treatment assignment probabilities for the first unit will be equal.]  ")
      }
    }
		
		if(substr(nnn,1,1) != "n"){
		assg.prob <- NULL
			for(ii in 1:n.tr){
				tmp <- readline(cat("Enter the assignment probability of experimental condition ", ii, ".", sep="")) 
				assg.prob <- append(assg.prob, tmp)
			}
			assg.prob <- as.numeric(assg.prob)
		}		
		
		## Set random seed:
    nnn <- readline("Would you like to specify a random seed for the initial assignment?  [y/n]  ")
		
			if(!(substr(nnn,1,1) %in% c("y", "n"))){
				ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
				if(substr(ddd, 1, 1) != "n"){
					}else{
						nnn <- readline("Would you like to specify a random seed for the initial experimental condition assignment?  [y/n]  ")
					}
			}
		
		if(substr(nnn,1,1) != "n"){
			seed <- readline("Enter the random seed.  ")
		}
		
				## ASSIGNMENT PROBABILITY STATISTIC:
		nnn <- readline("Would you like to specify the assignment probability summary statistic?  [n/y]  [If not, `mean' will be used.]  ")
		if(substr(nnn,1,1) == "y"){
			assg.prob.stat <- readline("Enter the summary statistic name.  [mean, median, trimmean]  ")
			if(assg.prob.stat == "trimmean"){
				ooo <- readline("Specify the proportion of blocks to be dropped from each end of the distribution before the mean is calculated.  [Defaults to 0.1]  ")
				if(substr(ooo,1,1) == ""){
					mtrim <- 0.1
				}else{
					mtrim <- ooo
				}
		}
		}else{
			assg.prob.stat <- "mean"
		}
		
		## ASSIGNMENT PROBABILITY METHOD:
		nnn <- readline("Would you like to specify the assignment probability algorithm?  [n/y]  [If not, `double' will be used.]  ")
		if(substr(nnn,1,1) == "y"){
			assg.prob.method <- readline("Enter the algorithm name.  [ktimes, fixed, prop, prop2, wprop]  ")
		}else{
			assg.prob.method <- "ktimes"
		}
		kfac <- NULL 
		
		if(assg.prob.method == "ktimes"){
			kfac <- as.numeric("Enter the value of k, the factor by which the most likely experimental condition will be multiplied, relative to the other conditions.  ")
		}
		
		if(assg.prob.method == "fixed"){
			assgpr <- readline("Enter 1st probability.  ")
			for(pc in 2:n.tr){
				assg.prob <- append(assg.prob, readline(cat("Enter probablity number ", pc, ".  ", sep="")))
			}
			assg.prob <- as.numeric(assg.prob)
		}
		
		## OUTPUT FILE NAME:
		nnn <- readline("Would you like to specify the output data file name?  [y/n]  [If not, `sbout1.RData' will be used.]  ")
		
			if(!(substr(nnn,1,1) %in% c("y", "n"))){
				ddd <- readline("The default is `yes'.  Continue? [y/n]  ")
				if(substr(ddd, 1, 1) != "n"){
					}else{
						nnn <- readline("Would you like to specify the output data file name?  [y/n]  [If not, `sbout1.RData' will be used.]  ")
					}
			}		
		
		if(substr(nnn,1,1) != "n"){
			file.name <- readline("Enter the file name.  Note: seqblock2k() expects a file of type `.RData'.  ")
		}						
	} ## END (query == T)
	
	## create vector of treatment names
	if(is.null(tr.names)){
		tr.names <- paste("Treatment", 1:n.tr)
	}

	## create kfac, if null
	if(!(is.null(assg.prob.kfac))){
		kfac <- assg.prob.kfac
	}
	
	## create vector of (equal) initial treatment probabilities
	if(is.null(assg.prob)){
		assg.prob <- rep(1/n.tr, n.tr)
	}
	
	## check that assg.prob sum to 1  
	if(sum(assg.prob)!=1){
		stop("Initial assignment probabilities do not sum to 1.\nRespecify and try again.")
	} 

	## check that if exact named, then supplied
	if((!is.null(exact.vars)) && is.null(exact.vals)){
		stop("Exact (grouped) blocking requested, but no values given.\nSpecify exact block values and try again.")
	} 
	
	## check that exact vars and vals are same length
	if(length(exact.vars) != length(exact.vals)){
		stop("Number of exact blocking variables does not equal number of values.\nSpecify exact block values and try again.")
	} 

	## check that if covars named, then supplied
	if((!is.null(covar.vars)) && is.null(covar.vals)){
		stop("Covariate blocking requested, but no values given.\nSpecify covariate values and try again.")
	} 
	
	## check that covar vars and vals are same length
	if(length(covar.vars) != length(covar.vals)){
		stop("Number of covariate blocking variables does not equal number of values.\nSpecify covariate block values and try again.")
	}
	
	## create variables
	lid <- length(id.vars)
	lex <- length(exact.vars)
	lcv <- length(covar.vars)

	## Add NA to each existing restriction set, 
	##   then check if any exact vals violate exact.restr
	if((lex > 0) && !(is.null(exact.restr))){
		for(i in names(exact.restr)){
			if(!(NA %in% exact.restr[[i]])){
				exact.restr[[i]] <- append(exact.restr[[i]], NA)
			}
			wexrstr <- which(exact.vars == i)
			if(!(exact.vals[wexrstr] %in% exact.restr[[exact.vars[wexrstr]]])){
				stop("Exact blocking value number ", wexrstr, " (", exact.vals[wexrstr], ") is not in the set of values to which exact blocking variable `", i, "' is restricted.  Respecify either the value, the restriction set, or both as needed." )
			}
		}
	}   
		
	## check if any covar vals violate covar.restr
	if((lcv > 0) && (!is.null(covar.restr))){
		for(i in names(covar.restr)){
			if(!(NA %in% covar.restr[[i]])){
				covar.restr[[i]] <- append(covar.restr[[i]], NA)
			}
			wcvrstr <- which(covar.vars == i)
			if(!(covar.vals[wcvrstr] %in% covar.restr[[covar.vars[wcvrstr]]])){
				stop("Covariate blocking value number ", wcvrstr, " (", covar.vals[wcvrstr], ") is not in the set of values to which covariate blocking variable `", i, "' is restricted.  Respecify either the value, the restriction set, or both as needed." )
			}
		}	
	}
	
	## set user-assigned seed
	if(!is.null(seed)){
		set.seed(seed)
	}
	
	## Draw initial treatment assignment
	init.tr <- sample(tr.names, 1, rep=F, prob = assg.prob)
	
	## Create data frame of unit 1 data
		## create id placeholders
	id.tmp <- rep(NA, lid)
		## create group placeholders
	ex.tmp <- rep(NA, lex)

		## create data frame
	x <- unlist(c(id.tmp, ex.tmp, unname(covar.vals), NA))
	x <- data.frame(t(x))
	colnames(x) <- c(id.vars, exact.vars, covar.vars, "Tr")
		## add id vals.  NOTE: will be all char or all num
	x[1, 1:lid] <- id.vals
		## add group vals.  NOTE: will be all char or all num
	if(!is.null(exact.vars)){
		x[1, (lid+1):(lid+lex)] <- exact.vals
	}
		## add initial treatment assignment
	x[1,ncol(x)] <- init.tr

	if(is.null(file.name)){
		file.name <- "sbout1.RData"
	}
	
	if(substr(file.name, start=nchar(file.name)-5, stop=nchar(file.name)) !=".RData"){
		warning("Destination file name does not end in .RData.")
	} 
	
	## Create storage list 'bdata'
	bdata <- list()
	bdata$x <- x
	bdata$nid <- id.vars
	bdata$nex <- exact.vars
	bdata$ncv <- covar.vars
	bdata$rex <- exact.restr  ## EXACT restricted values list
  if(!is.null(bdata$rex)){
    names(bdata$rex) <- exact.vars
  }
	bdata$rcv <- covar.restr  ## BLOCK restricted values list
  if(!is.null(bdata$rcv)){
    names(bdata$rcv) <- covar.vars
  }
	bdata$ocv <- covars.ord   ## block covariates order
	bdata$trn <- tr.names
	bdata$apstat <- assg.prob.stat 
	bdata$mtrim <- trim
	bdata$apmeth <- assg.prob.method
	bdata$kfac <- kfac ## multiple for method 'ktimes'
	bdata$assgpr <- assg.prob
	bdata$datetime <- date()
	bdata$orig <- x
		
	## Write bdata to file
	save(bdata, file = file.name)
	if(verbose == TRUE){
		cat("Unit 1 data stored as file ", file.name, ".\nThe current working directory is ", getwd(), "\n", sep="")
		cat("Unit ", nrow(x), " assigned to ", init.tr, ".\n", sep="")
		cat("The new data as entered:\n")
		print(x)
	}	
	return(bdata)	
}
